﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Net;
using System.Net.Sockets;
using System.IO;
using System.Threading;

namespace NetworkClient
{
    public partial class Form1 : Form
    {
        #region 常量定义
        //客户端
        private TcpClient tcpClient = null;
        private NetworkStream networkStream = null;
        private BinaryReader reader = null;
        private BinaryWriter writer = null;

        private object lockObj = new object();

        //申明委托
        //显示消息
        private delegate void ShowMessage(string str);
        private ShowMessage showMessageCallback;

        //显示状态
        private delegate void ShowStatus(string str);
        private ShowStatus showStatusCallback;

        #endregion

        public Form1()
        {
            InitializeComponent();

            #region  实例化委托
            //显示消息
            showMessageCallback = new ShowMessage(showMessage);

            //显示状态
            showStatusCallback = new ShowStatus(showStatus);

            #endregion
        }

        #region 定义回调函数

        //显示消息
        private void showMessage(string str)
        {
            listBox_receive.Items.Add(tcpClient.Client.RemoteEndPoint);
            listBox_receive.Items.Add(str);
            listBox_receive.TopIndex = listBox_receive.Items.Count - 1;
        }

        //显示状态
        private void showStatus(string str)
        {
            toolStripLab_state.Text = str;
        }

        //重置消息
        private void resetMessage()
        {
            tBox_send.Text = "";
            tBox_send.Focus();
        }

        #endregion


        private void btn_connect_Click(object sender, EventArgs e)
        {
            Thread connectThread = new Thread(connectToServer);
            connectThread.Start();

        }

        /// <summary>
        /// 连接服务器
        /// </summary>
        private void connectToServer()
        {
            try
            {
                statusStrip_Info.Invoke(showStatusCallback, "正在连接...");
                if (tBox_ip.Text == string.Empty || tBox_port.Text == string.Empty)
                {
                    MessageBox.Show("请先输入服务器的IP地址和端口号");
                }
                IPAddress ipaddress = IPAddress.Parse(tBox_ip.Text);
                tcpClient = new TcpClient();
                tcpClient.Connect(ipaddress, int.Parse(tBox_port.Text));

                if (tcpClient != null)
                {
                    statusStrip_Info.Invoke(showStatusCallback, "连接成功");
                    networkStream = tcpClient.GetStream();
                    reader = new BinaryReader(networkStream);
                    Thread receiveThread = new Thread(receiveMessage);
                    receiveThread.Start();

                    writer = new BinaryWriter(networkStream);
                }
            }
            catch(Exception ex)
            {
                statusStrip_Info.Invoke(showStatusCallback, "连接失败");
                closeConnect();
                statusStrip_Info.Invoke(showStatusCallback, "就绪");
            }
        }

        /// <summary>
        /// 接收文件
        /// </summary>
        private void receiveMessage()
        {
            while (reader != null)
            {
                try
                {
                    string sReceiveMsg = reader.ReadString();
                    listBox_receive.Invoke(showMessageCallback, sReceiveMsg);
                }
                catch (System.Exception ex)
                {
                    closeConnect();
                    listBox_receive.Invoke(showStatusCallback, "断开连接");
                }
            }
        }

        /// <summary>
        /// 关闭连接
        /// </summary>
        private void closeConnect()
        {
            lock (lockObj)
            {
                if (reader != null)
                {
                    reader.Close();
                    reader = null;
                }
                if (writer != null)
                {
                    writer.Close();
                    writer = null;
                }
                if (tcpClient != null)
                {
                    tcpClient.Close();
                    tcpClient = null;
                }
            }
        }

        /// <summary>
        /// 断开和服务器的网络连接
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void btn_disconnect_Click(object sender, EventArgs e)
        {
            closeConnect();

            toolStripLab_state.Text = "断开连接";
        }

        /// <summary>
        /// 发送数据
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void btn_send_Click(object sender, EventArgs e)
        {
            if (writer != null)
            {
                try
                {
                    toolStripLab_state.Text = "正在发送...";
                    writer.Write(tBox_send.Text);
                    writer.Flush();
                    toolStripLab_state.Text = "发送完毕";
                    resetMessage();
                }
                catch (System.Exception ex)
                {
                    closeConnect();
                    toolStripLab_state.Text = "断开连接";
                }
            }
        }

        private void Form1_FormClosed(object sender, FormClosedEventArgs e)
        {
            closeConnect();
        }
    }
}
